﻿using FileSystem.Impl;
using FileSystem.Utility;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace FileSystem.impl.Commands
{
    class Rename : ICommand, ICommandPrototype
    {
        private static Rename zombie;

        private static void loadEmulator()
        {
            zombie = new Rename(new HelpDescription() { Name = "rename", Description = "Renames a file/directory." });
            ICommandPrototypeRegistry r = AppResources.getInstance().getCommandRegistry();
            r.register("rename", zombie);
        }

        private IFSDirectory cwd;
        private String filename;
        private String newFileName;
        private bool executeSucceeded;

        public IHelpDescription Description
        {
            get;
            private set;
        }
        private Rename(IHelpDescription helpDescription)
        {
            //for zombie
            this.Description = helpDescription;
        }

        private Rename(String filename, String newFileName)
        {
            this.filename = filename;
            this.newFileName = newFileName;
            executeSucceeded = false;
        }

        public ICommand clone()
        {
            //Cannot clone touch without name of file as arg.
            return null;
        }

        public ICommand clone(String arg)
        {
            string fileNAme = StringUtil.firstToken(arg);
            string newfilename = StringUtil.remainder(arg);
            Rename rc = new Rename(fileNAme, newfilename);
            return rc;
        }

        public IResult execute()
        {
            this.cwd = AppResources.getInstance().getFileSystem().CurrentDirectory;
            IFSNode node = AppResources.getInstance().getFileSystem().CurrentDirectory.GetByName(filename);
            if (node != null)
            {
                node.rename(newFileName);
                return new Result("rename successful: " + node.describe());
            }
            else
            {
                return new Result(true, "rename failed.");
            }

        }

        public void undo()
        {
            if (!executeSucceeded)
            {
                //nothing to do, because execution failed...
                //we don't want to remove the node that might have been there of the same name.
                return;
            }
            cwd.removeNode(filename);
        }

        public IResult redo()
        {
            return execute();
        }

        public String describe(IPrintContext context)
        {
            return context.getFormattedString("rename " + filename + "(" + executeSucceeded + ").");
        }


    }
}
